<?php
/**
 * Created by PhpStorm.
 * User: Administrator
 * Date: 14-5-15
 * Time: 下午11:38
 */
namespace ulue\parts\session\handler;
use Ulue;
// use ulue\core\utils\OpreateObjectAsArray;
use Debug;

class GSession extends \ArrayObject
{
    static private $owner             = null;           // session对象
    static private $session           = [];             // 原始session
    public  static $encryptSession    = [];             // 加密后的session
    private $encryptKey               = '_empty';       // 加密key
    public   $defaultSet              = [];


    public function __construct(array $config=[] )
    {
        $this->defaultSet = array_merge( Ulue::$app->get('session') , $config );
    }

    /**
     * session_start()
     * session_encode()
     * session_decode()
     * */
    static public function owner()
    {
        if (self::$owner === null)
        {
            return self::$owner = new self($config=array());
        }

        return self::$owner;
    }

    public function start()
    {
        \Debug::trace("i 准备开启session会话。");
        $this->initSession();
        if ( self::isStarted() === false ) {
            session_start();
        }
    }

    public function restart()
    {

    }

    //session 初始化配置
    private function initSession()
    {
        $config                     = $this->defaultSet;
        $config['name']             = isset($config['name']) ? $config['name']  : 'INHERE' ;// PHPSESSID
        $config['path']             = isset($config['path']) ? $config['path']  : '' ;
        $config['domain']           = isset($config['domain'])?  $config['domain'] : '' ;
        $config['use_trans_sid']    = isset($config['use_trans_sid']) ? $config['use_trans_sid'] : 0;
        $config['use_cookies']      = isset($config['use_cookies'])?  $config['use_cookies']: 1;
        $config['cache_limiter']    = isset($config['cache_limiter']) ? $config['cache_limiter'] :';' ;
        $config['cache_expire']     = (isset($config['cache_expire']) ? $config['cache_expire']: 10)*60 ;
        $config['cache_lifetime']   = isset($config['cache_lifetime']) ? $config['cache_lifetime']: 0 ;
        $config['maxlifetime']      = (isset($config['maxlifetime']) ? $config['maxlifetime'] : 11)*60 ;
        //isset($config['type'])  || Ulue::$app->get('session.handle',$config['type']);

        @ini_set('session.auto_start', 0);//0 不自动开启session 1 自动开启
        @ini_set('session.use_trans_sid',   $config['use_trans_sid'] );//是否使用明码在URL中显示SID（会话ID），默认是禁止
        @ini_set('session.use_cookies',     $config['use_cookies'] );
        @ini_set('session.cookie_domain',   $config['domain'] );
        @ini_set('session.cache_expire',    $config['cache_expire'] );//客户端session cookie存储时间 （分钟）
        @ini_set('session.gc_maxlifetime',  $config['maxlifetime'] ); //服务端session file存储过期时间 （分钟）

        session_name($config['name']);
        session_save_path($config['path']);
        session_cache_limiter($config['cache_limiter']);
        // session_cache_expire($config['cache_expire']);

    }

    public function setIniOfSession($value='')
    {
      # code...
    }

    /**
     * @param $name
     * @param $value
     * @param string $suffix 给加密后的value加上一段 常量字符串，
     * ex:保存登陆用户名到session，用户id -->$suffix;$_SESSION['username'] = $value.$suffix
     * @param null $type 是否加密
     * @return bool
     */
    static public function create($name,$value,$suffix=NULL,$type=true)
    {
        Debug::trace("i 添加session",['@param $name'=>$name,'@param $value'=>$value]);

        if ( is_null($name) ) {
          return false;
        }

        if (is_string($name))
        {
            $name                               = trim($name);
            self::$session[$name]               = $value;
            #值加密存储
            $_SESSION[$name]                    = is_null($suffix)? $value: $value.$suffix;

            return $_SESSION[$name];
        } else {

            return false;
        }
    }
    //create alias
    static public function set($name,$value,$suffix=NULL,$type=null)
    {
        return static::create($name,$value,$suffix,$type);
    }

    /**
     * @param null $name
     * @param bool|int $type $name名称存储时是否是加密的，默认是认为加密过的
     * @return bool
     */
    static public function read($name=Null,$type=true)
    {
        if (is_null($name)) {

          return $_SESSION;
        }

        Debug::trace("i 读取session",['@param $name'=>$name]);

        if (is_string($name))
        {
            $name = trim($name);

            //默认加密存储 name
            if ($type)
            {
                $name = static::encryption($name);
            }

            return isset($_SESSION[$name])?$_SESSION[$name]:false;
        } else {

            return false;
        }
    }

    //read alias
    static public function get($name=Null,$type=false)
    {
        return static::read($name,$type);
    }

    static public function destroy()
    {
        foreach ($_SESSION as $name => $value) {
            session_unset($_SESSION[$name]);
            unset($_SESSION[$name]);
        }

        return true;
    }
    //destroy alias
    static public function delete($name=Null)
    {
        session_unset($name);
        unset($_SESSION[$name]);
    }



    /**
     * 简单加密
     * @param $data
     * 1. $data--array object string int md5(serialize($var));
     * 2. $data--string int  md5($salt.$password);
     * @param string $salt
     * @param int $type
     * @param string $fun
     * @return bool
     */
    private function encryption($data,$type=1,$salt=null,$fun='md5')
    {
        $salt = is_null($salt) ?
                Ulue::$app->get('session.encrypt.name_salt') :
                $salt;

        switch( (int)$type )
        {
            case 1:             //MD5(value)加密
                $encrypt_data = $fun($data);
                break;
            case 2:             //MD5(常量+value)加密
                $encrypt_data = $fun($salt.$data);
                break;
            case 3:             //MD5(serialize(value))先序列化，再加密
                $encrypt_data = $fun(serialize($data));
                break;
            default: return false;
        }

        return $encrypt_data;
    }

    static public function isStarted()
    {
        if ( php_sapi_name() !== 'cli' ) {
            if ( version_compare(phpversion(), '5.4.0', '>=') ) {

                return session_status() === PHP_SESSION_ACTIVE ? TRUE : FALSE;
            } else {

                return session_id() === '' ? FALSE : TRUE;
            }
        }

        return FALSE;
    }

    //\Ulue::$app->session>name = value
    public function __set($name,$value)
    {
        if (isset($this->$name))
        {
          $this->$name = $value;
        }
        $_SESSION[$name] = $value;
    }

    // \Ulue::$app->session>name
    public function __get($name)
    {
        \Debug::trace('i 获取session ','Var Name: '.$name);

        if (isset($_SESSION[$name])) {

            return $_SESSION[$name];
        }
        else if (isset($this->$name))
        {

            return $this->$name;
        }
        else {

            return NULL;
        }
    }
}